package com.aaa.data;

import com.aaa.config.SSLHelper;
import com.aaa.config.ThreadExecutorConfig;
import com.aaa.dto.BookCatalogueDto;
import com.aaa.entity.BookCatalogue;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;
import org.jsoup.nodes.Node;
import org.jsoup.select.Elements;

import java.io.IOException;
import java.math.BigInteger;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import static com.aaa.util.DataProcessing.splitList;

/**
 * @author 杨森
 * @version 1.0
 * @Title: BookCatalogue
 * @date 2020/8/7 15:39
 */
public class BookCatalogueDB {

    private static ExecutorService executorService;

    public static List<BookCatalogueDto> setDataSource(String dataSource, String bookCod, ExecutorService executorService) {
        BookCatalogueDB.executorService = executorService;
        switch (dataSource) {
            case "biquge5200":
                return biquge5200(bookCod);
            case "biquge":
                return biquge(bookCod);
            case "ddxs":
                return ddxs(bookCod);
        }
        return null;
    }

    private static List<BookCatalogueDto> ddxs(String bookCod) {
        try {
            Pattern pattern = Pattern.compile("<a\\s*href=\"?([\\w\\W]*?)\"?[\\s]*?[^>]>([\\s\\S]*?)(?=</a>)");
            Map<Integer, List<BookCatalogueDto>> bookCatalogueDtoMaps = new HashMap<>(3);
            Document document = Jsoup.connect("http://www.ddxs.com/"+bookCod+"/").get();
            Element tbody = document.getElementsByTag("tbody").get(1);
            Elements td = tbody.getElementsByTag("td");
            Map<Integer, List<Element>> integerListMap = splitList(td, 3);
            CountDownLatch latch = new CountDownLatch(3);
            for (int i = 0; i < 3; i++) {
                final int ins = i;
                executorService.execute(() -> {
                    bookCatalogueDtoMaps.put(ins, get1(integerListMap.get(ins), bookCod, document, pattern));
                    latch.countDown();
                });
            }
            latch.await();
            List<BookCatalogueDto> bookCatalogueDtos = new ArrayList<>(td.size());
            for (int i = 0; i < 3; i++) {
                bookCatalogueDtos.addAll(bookCatalogueDtoMaps.get(i));
            }
            return bookCatalogueDtos;
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            executorService.shutdown();
        }
        return null;
    }

    private static List<BookCatalogueDto> biquge5200(String bookCod) {
        try {
            Map<Integer, List<BookCatalogueDto>> bookCatalogueDtoMaps = new HashMap<>(3);
            Pattern pattern = Pattern.compile("<a\\s*href=\"?([\\w\\W]*?)\"?[\\s]*?[^>]>([\\s\\S]*?)(?=</a>)");
            Document document = Jsoup.connect("https://www.biquge5200.com/" + bookCod + "/").get();
            Elements dd = document.getElementsByTag("dd");
            Map<Integer, List<Element>> integerListMap = splitList(dd, 3);
            CountDownLatch latch = new CountDownLatch(3);
            for (int i = 0; i < 3; i++) {
                final int ins = i;
                executorService.execute(() -> {
                    bookCatalogueDtoMaps.put(ins, get(integerListMap.get(ins), bookCod, document, pattern));
                    latch.countDown();
                });
            }
            latch.await();
            List<BookCatalogueDto> bookCatalogueDtos = new ArrayList<>(dd.size());
            for (int i = 0; i < 3; i++) {
                bookCatalogueDtos.addAll(bookCatalogueDtoMaps.get(i));
            }
            return bookCatalogueDtos;
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            executorService.shutdown();
        }
        return null;
    }

    public static List<BookCatalogueDto> get1(List<Element> tds, String bookCod, Document document, Pattern pattern) {
        try {
            Element btitle = document.getElementsByClass("btitle").get(0);
            //书名
            Elements h1 = btitle.getElementsByTag("h1");
            Element intro = document.getElementsByClass("intro").get(0);
            Element elementsByClass = document.getElementsByClass("pic").get(0);
            String pic = elementsByClass.getElementsByTag("img").toString().replace("src=\"","src=\"http://www.ddxs.com");
            String bookAuthor = btitle.getElementsByTag("i").get(0).text().replace("作者：", "");
            List<BookCatalogueDto> bookCatalogueDtos = new ArrayList<>(tds.size());
            tds.stream().forEach(td -> {
                BookCatalogueDto bookCatalogueDto = new BookCatalogueDto();
                Elements as = td.getElementsByTag("a");
                if(as.size()==0){
                    return;
                }
                Element a = as.get(0);
                bookCatalogueDto.setCatalogueName(a.text());
                String href = a.attr("href").replace(bookCod,"").replace("/","").replace(".html","");
                bookCatalogueDto.setBookImage(pic);
                bookCatalogueDto.setCatalogueCod(Integer.valueOf(href));
                bookCatalogueDto.setBookName(h1.text());
                bookCatalogueDto.setBookIntro(intro.text().replace("小说介绍：",""));
                bookCatalogueDto.setBookCod(bookCod);
                bookCatalogueDto.setBookAuthor(bookAuthor);
                bookCatalogueDtos.add(bookCatalogueDto);
            });
            return bookCatalogueDtos;
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    public static List<BookCatalogueDto> get(List<Element> dd, String bookCod, Document document, Pattern pattern) {
        List<BookCatalogueDto> bookCatalogueDtos = new ArrayList<>(dd.size());
        Element imgurl = document.getElementById("fmimg");
        Element intro = document.getElementById("intro");
        Element info = document.getElementById("info");
        Element child = info.child(1);
        String h1 = info.select("h1").text();
        for (int i = 0; i < dd.size(); i++) {
            Element element = dd.get(i);
            BookCatalogueDto bookCatalogueDto = new BookCatalogueDto();
            BookCatalogue bookCatalogue = new BookCatalogue();
            Node node = element.childNode(0);
            for (Node e : element.childNodes()) {
                if (!"".equals(e.toString())) {
                    node = e;
                }
            }
            bookCatalogueDto.setCatalogueName(node.childNode(0).toString());
            String s1 = node.toString();
            Matcher matcher = pattern.matcher(s1);
            if (matcher.find()) {
                String nameCodeUrl = matcher.group(1);
                String insStr = nameCodeUrl.substring(nameCodeUrl.lastIndexOf("/") + 1, nameCodeUrl.lastIndexOf("."));
                bookCatalogueDto.setCatalogueCod(Integer.parseInt(insStr));
            }
            bookCatalogueDto.setBookName(h1);
            bookCatalogueDto.setBookIntro(intro.text());
            for (Node n : imgurl.childNodes()) {
                if (n.toString().matches("(.*)img(.*)")) {
                    bookCatalogueDto.setBookImage(imgurl.childNode(0).toString());
                }
            }
            bookCatalogueDto.setBookCod(bookCod);
            bookCatalogueDto.setBookAuthor(child.text().replace("作 者：", ""));

            bookCatalogueDtos.add(bookCatalogueDto);
            if (i + 1 < dd.size()) {
                Node node1 = dd.get(i + 1).childNode(0);
                Matcher matcher1 = pattern.matcher(node1.toString());
                if (matcher1.find()) {
                    String nameCodeUrl = matcher.group(1);
                    String insStr = nameCodeUrl.substring(nameCodeUrl.lastIndexOf("/") + 1, nameCodeUrl.lastIndexOf("."));
                    bookCatalogue.setNextCode(Integer.parseInt(insStr));
                }
            }

        }
        return bookCatalogueDtos;
    }

    private static List<BookCatalogueDto> biquge(String bookCod) {
        try {
            Pattern pattern = Pattern.compile("<a\\s*href=\"?([\\w\\W]*?)\"?[\\s]*?[^>]>([\\s\\S]*?)(?=</a>)");
            Document document = Jsoup.connect("https://www.biquge.com/" + bookCod + "/").get();

            Map<Integer, List<BookCatalogueDto>> bookCatalogueDtoMaps = new HashMap<>(3);
            Elements dd = document.getElementsByTag("dd");
            Map<Integer, List<Element>> integerListMap = splitList(dd, 3);
            CountDownLatch latch = new CountDownLatch(3);

            for (int i = 0; i < 3; i++) {
                final int ins = i;
                executorService.execute(() -> {
                    bookCatalogueDtoMaps.put(ins, get(integerListMap.get(ins), bookCod, document, pattern));
                    latch.countDown();
                });
            }
            latch.await();
            List<BookCatalogueDto> bookCatalogueDtos = new ArrayList<>(dd.size());
            for (int i = 0; i < 3; i++) {
                bookCatalogueDtos.addAll(bookCatalogueDtoMaps.get(i));
            }
            return bookCatalogueDtos;
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            executorService.shutdown();
        }
        return null;
    }
}
